/* Display.h
Copyright (c) 2008 Michael Zahniser
Please note the license terms (MIT license) at the end of this document.

Header file for the Display class, which displays task lists that are being edited
and handles or forwards all events.
*/

#ifndef __MZ_DISPLAY_H__
#define __MZ_DISPLAY_H__

#include "_common/Noncopyable.h"

#include "TaskList.h"
#include "Icons.h"
#include "Editor.h"
#include "_sdl/Window.h"
#include "_sdl/Font.h"
#include "_sdl/Color.h"

#include <string>
#include <map>

using std::string;
using std::map;



class Display : public Noncopyable {
public:
	// Constructor. Takes as an argument the directory containing the resource files.
	Display(string resourcePath, string filePath);
	// Destructor. Saves changes to the files.
	~Display();

	// Begin the event loop.
	// This function blocks until the user quits.
	void Run();


private:
	// Load the named file, and update the "Recent Files" preference.
	void LoadFile(string path);
	
	// Handle events. Returns false if the view should not be redrawn.
	bool HandleKey(const SDL_Event &event);
	bool HandleButton(const SDL_Event &event);
	bool HandleClick(const SDL_Event &event);
	bool HandleScroll(const SDL_Event &event);
	bool HandleDrag(const SDL_Event &event);

	// Apply any changes that have been made to the preferences.
	bool LoadPreferences();
	// These functions are called by LoadPreferences().
	bool SetDimensions();
	void SetColors();

	// Redraw the window.
	void Draw();

	// Draw individual regions of the window.
	void DrawCategories();
	void DrawScrollBar();
	bool UpdateScrollPosition();
	void DrawSelection();
	void DrawTasks();
	void DrawStatus();
	
	// Load user preferences from the given TaskList and store them in the given map.
	// This can load any data type that has an istream operator>>.
	template <class Type>
	static void LoadPreferences(const TaskList &taskList, map<string, Type> &preferences);
	
	// Move the scroll bar to the given height, limiting it to its allowable
	// range of travel.
	void MoveScrollBar(int y);

	// Toggle between the given editor and the main editor.
	// If the previous editor was the preferences, apply the preference changes.
	void ToggleEditor(Editor &toggle);


private:
	// Flag storing whether construction was successful.
	bool isInitialized;

	// The SDL surface on which everything will be displayed.
	Window screen;

	// Font used to draw all text.
	Font font;
	// Glyphs for the different icons.
	Icons icons;
	
	// Pointer to the editor that is currently being used. Depending on the mode
	// this may be the main editor, the help editor, or the preferences editor.
	Editor *editor;

	// Current position of the scroll bar. The mouse-driven scroll position is
	// overridden as soon as the user tries to edit the list.
	int scroll;
	int mouseScroll;
	bool scrollBarIsVisible;
	
	// Editors for the main file, the help, and the preferences. This allows the
	// three different modes to each remember their full edit state (which list is
	// selected, what text is being entered, etc.).
	Editor fileEditor;
	Editor helpEditor;
	Editor preferencesEditor;

	// Colors and window region dimensions specified by the preferences.
	map<string, Color> color;
	map<string, int> dimension;
	
	// Status string. Pops up a box informing the user of events such as saving the
	// file or reverting.
	string status;
	

private:
	// Height of one row of the list. This is also the dimensions of the icons,
	// which are all square.
	int ROW_HEIGHT;
	// Y offset of the text line relative to the top of a row of the list.
	// The offset is such that the bottom of the text is the bottom of the row.
	int TEXT_Y_OFFSET;
	// Number of rows of the list that are visible in the editor, rounded up.
	int VISIBLE_ROWS;

	// Regions of the screen, defined by user preferences.
	Rectangle CATEGORY_RECT;
	Rectangle DIVIDER_RECT;
	Rectangle TREE_RECT;
	Rectangle SCROLL_TREE_RECT;
	Rectangle SCROLL_BAR_RECT;
	Rectangle STATUS_RECT;
	Rectangle STATUS_FRAME;
	
	
private:
	// Function that determines whether or not a given SDL_Event needs to be processed.
	static int EventFilter(const SDL_Event *event);
};



#endif

/* Copyright (c) 2008 Michael Zahniser

Permission is hereby granted, free of charge, to any person
obtaining a copy of this software and associated documentation
files (the "Software"), to deal in the Software without
restriction, including without limitation the rights to use,
copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the
Software is furnished to do so, subject to the following
conditions:

The above copyright notice and this permission notice shall be
included in all copies or substantial portions of the Software.

THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
OTHER DEALINGS IN THE SOFTWARE. */
